package com.example.config;

import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.core.Binding;
import org.springframework.amqp.core.BindingBuilder;
import org.springframework.amqp.core.Queue;
import org.springframework.amqp.core.TopicExchange;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.amqp.rabbit.retry.MessageRecoverer;
import org.springframework.amqp.rabbit.retry.RepublishMessageRecoverer;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @author yinxin
 * @version 1.0
 * @Description: 消费异常配置
 * @date 2022/6/1014:21
 */
@Configuration
@Slf4j
public class RabbitMQErrorConfig {

    //发生异常的交换机
    private String orderErrorExchange = "order.error.exchange";

    //发生异常的队列
    private String orderErrorQueue = "order.error.queue";

    //发生异常的routing.key
    private String orderErrorRoutingKey = "order.error.routing.key";

    @Autowired
    RabbitTemplate rabbitTemplate;

    @Bean
    public TopicExchange errorTopicExchange(){
        //名字、是否持久化和是否自动删除
        return new TopicExchange(orderErrorExchange,true,false);
    }

    @Bean
    public Queue errorQueue(){
        return new Queue(orderErrorQueue,true);
    }

    /**
     * 根据routingKey绑定异常交换机和异常队列
     */
    @Bean
    public Binding bindingErrorQueueAndExchange(){
        return BindingBuilder.bind(errorQueue()).to(errorTopicExchange()).with(orderErrorRoutingKey);
    }

    /**
     * 异常队列必须要设置的东西
     * 消息重试一定次数后,用特定的routingKey转发到指定的交换机中,方便后续排查和告警
     */
    @Bean
    public MessageRecoverer messageRecoverer(){
        return new RepublishMessageRecoverer(rabbitTemplate, orderErrorExchange, orderErrorRoutingKey);
    }
}
